(() => {
    // 3.方法装饰器
    /**
     *  它被应用到方法的属性描述符上，可以用来监视，修改或者替换方法定义
     *  方法装饰会在运行时传入以下三个参数
     *  (1).对于静态成员来说是类的构造函数，对于实例成员来说是类的原型对象
     * 
     *  (2).成员的名字
     * 
     *  (3).成员的属性描述符
     */

    function get(params: string) {
        return (target: any, methodName: string, desc: any) => {
            console.log(target);
            console.log(methodName);
            console.log(desc);
            // target
            target.apiUrl = '修改属性'
            target.run = () => {
                console.log('我是修改跑的方法');
            }
            let oMethod = desc.value
            desc.value = (...args: any[]) => {
                args = args.map(item => {
                    return String(item)
                })
                // oMethod.apply(this, args)
            }
        }
    }
    class HttpClient {
        public url: any | undefined
        constructor() { }
        @get('修改方法')
        getData(...args: any[]) {
            console.log(args);
            console.log('我是类的方法');
        }
    }
    const http = new HttpClient()
    http.getData(1, '2')


    // 4.方法参数装饰器
    /**
     *  参数装饰器表达式会在运行时当作函数被调用，可以使用参数装饰器为类的原型增加一些元素数据，传入以下三个参数
     *  (1).对于静态成员来说是类的构造函数，对于实例成员是类的原型对象
     * 
     *  (2).方法的名字
     * 
     *  (3).参数在函数参数列表中的索引
     */
    function logParams(params: string) {
        return (target: any, methodName: string, paramsIndex: number) => {
            console.log(params);
            console.log(target);
            console.log(methodName);
            console.log(paramsIndex);
        }
    }
    class HttpClient2 {
        public url: string
        constructor() { }
        getData(@logParams('uuid') uuid: any) {
            console.log('我是getData里面的方法');
        }
    }
    const http2 = new HttpClient2()
    http.getData()
})()